package com.liyong.pullorder.sdk.autoconfigure;

import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;

import java.util.HashMap;
import java.util.Map;

/**
 * @author 葡萄味的萝卜
 * @date 2025/10/21 09:56
 * 拉单SDK统一配置属性类
 * 核心作用：将application.yml中的分散配置集中管理，支持多平台差异化配置
 * 设计目标：通过配置化实现新平台快速接入，避免代码修改
 * 配置示例：
 * pull:
 *   order:
 *     sdk:
 *       http-client:
 *         max-total: 200
 *       platforms:
 *         huawei:
 *           base-url: https://api.huawei.com
 *           auth:
 *             type: OAUTH2
 *
 */
@ConfigurationProperties(prefix = "pull-order-sdk")
@Data
public class PullOrderSdkProperties {
    // 是否启用SDK，默认true
    private boolean enabled = true;
    // HTTP连接池配置 - 应对不同平台网络稳定性差异
    private HttpClient httpClient = new HttpClient();
    // 重试机制配置 - 实现指数退避重试
    private Retry retry = new Retry();
    // Sentinel限流降级配置 - 保障系统稳定性
    private Sentinel sentinel = new Sentinel();
    // 各平台具体配置，key为平台编码，如huawei、honor等，支持10+平台差异化配置
    private Map<String, PlatformConfig> platforms = new HashMap<>();

    /**
     * HTTP客户端配置内部类，连接池配置
     * 作用：配置连接池、超时时间等网络相关参数
     * 解决痛点：各平台网络环境差异导致的连接超时、性能不稳定问题
     */
    @Data
    public static class HttpClient {
        // 连接池最大连接数，支撑10万+日订单量
        private int maxTotal = 200;
        // 每个路由的最大连接数
        private int maxPerRoute = 50;
        // 连接超时时间(毫秒)
        private int connectTimeout = 5000;
        // 读取超时时间(毫秒)
        private int socketTimeout = 30000;
        // 从连接池获取连接的超时时间(毫秒)
        private int connectionRequestTimeout = 2000;
    }

    /**
     * 重试机制配置内部类
     * 作用：配置失败重试策略，支持指数退避
     * 集成Spring @Retryable，实现智能重试策略
     */
    @Data
    public static class Retry {
        // 最大重试次数，第一次请求失败后，会进行重试，重试次数为3次
        private int maxAttempts = 3;
        // 重试间隔(毫秒)，第一次请求失败后，会进行重试，重试间隔为1秒
        private long backoff = 1000;
        // 重试间隔倍数，
        // 第一次请求失败后，会进行重试，重试间隔为1秒
        // 第二次请求失败后，会进行重试，重试间隔为2秒
        // 第三次请求失败后，会进行重试，重试间隔为4秒
        private double multiplier = 2.0;
    }

    /**
     * Sentinel限流配置内部类
     * 作用：配置QPS限流和降级策略
     * 防止异常流量冲击下游系统，保障分钟级准实时拉取稳定性
     */
    @Data
    public static class Sentinel {
        // 是否启用Sentinel
        private boolean enabled = true;
        // 每秒查询率限制
        private int qps = 100;
        // 限流或降级时的提示信息
        private String fallbackMsg = "系统繁忙，请稍后重试";
    }

    /**
     * 平台配置内部类
     * 作用：为每个对接平台配置独立的API地址、认证方式和数据格式
     * 每个对接平台独立配置，新平台接入只需新增配置项
     */
    @Data
    public static class PlatformConfig {
        // 平台API基础地址
        private String baseUrl;
        // 认证配置
        private AuthConfig auth;
        // 数据解析配置，解析器配置
        private ParserConfig parser;
        // 自定义请求头
        private Map<String, String> headers = new HashMap<>();
    }

    /**
     * 认证配置内部类
     * 作用：配置平台的认证方式和相关参数
     * 统一认证配置
     * 封装OAuth2、API Key等多种认证方式，配置化适配新平台
     */
    @Data
    public static class AuthConfig {
        // 认证类型：OAUTH2、API_KEY等
        private String type;
        // 认证参数，如clientId、clientSecret、apiKey等
        private Map<String, String> config = new HashMap<>();
    }

    /**
     * 数据解析配置内部类
     * 作用：配置数据格式和字段映射规则
     * 数据解析配置
     * 定义XML/JSON格式映射规则，完成标准化数据清洗
     */
    @Data
    public static class ParserConfig {
        // 数据格式：JSON、XML
        private String type;
        // 字段映射规则，如平台字段名->标准字段名
        private Map<String, String> mapping = new HashMap<>();
    }

}
